package com.nononsenseapps.feeder.mobile.ui

import android.content.Intent
import androidx.activity.OnBackPressedCallback
import androidx.appcompat.app.ActionBarDrawerToggle
import androidx.appcompat.widget.Toolbar
import androidx.core.view.GravityCompat
import androidx.drawerlayout.widget.DrawerLayout
import androidx.lifecycle.lifecycleScope
import androidx.navigation.ui.AppBarConfiguration
import androidx.navigation.ui.setupWithNavController
import androidx.recyclerview.widget.RecyclerView
import com.gitee.wsl.ext.base.isFalse
import com.google.android.material.appbar.MaterialToolbar
import com.leinardi.android.speeddial.AdvSpeedDialView
import com.leinardi.android.speeddial.DragDoubleTouchViewAdapter
import com.nononsenseapps.feeder.db.ARG
import com.nononsenseapps.feeder.db.room.ID_ALL_FEEDS
import com.nononsenseapps.feeder.mobile.R
import com.nononsenseapps.feeder.mobile.ui.feed.FeedFragment
import com.nononsenseapps.feeder.ui.AbstractFeedActivity
import com.nononsenseapps.feeder.ui.home.FeedsAdapter
import com.nononsenseapps.feeder.ui.reader.webview.ReaderWebViewFragment
import com.nononsenseapps.feeder.util.*
import kotlinx.coroutines.*
import timber.log.Timber


class FeedActivity :  AbstractFeedActivity() {

    private lateinit var toolbar : MaterialToolbar
    private lateinit var drawerLayout : DrawerLayout
    private lateinit var navDrawerList : RecyclerView

    private lateinit var fabButton : AdvSpeedDialView

    override fun initFeedActivityView() {
        setContentView(R.layout.activity_navigation)
        toolbar = findViewById(R.id.toolbar)
        setSupportActionBar(toolbar)

        drawerLayout=findViewById(R.id.drawer_layout)
        navDrawerList=findViewById(R.id.navdrawer_list)
        fabButton = findViewById(R.id.fab)

        val toggle = ActionBarDrawerToggle(
            this, drawerLayout, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close)
        drawerLayout.addDrawerListener(toggle)
        toggle.syncState()

        val appBarConfiguration = AppBarConfiguration(navController.graph, drawerLayout)
        toolbar.setupWithNavController(navController, appBarConfiguration)

        fabButton.setClickCallback {
            fabClickListener?.fabOnClickListener()
        }

        fabButton.setDoubleClickCallback {
            fabClickListener?.fabOnDoubleClickListener()
        }

        fabButton.setLongClickCallback{
            fabClickListener?.fabOnLongClickListener()
        }

        fabButton.setOnActionSelectedListener {
            fabClickListener?.onActionSelected(it)
            false
        }

        fabButton.setHalfHoveringStateChangeCallback(object: DragDoubleTouchViewAdapter.HalfHoveringStateChangeCallback{
            override fun isHalfHoveringAble(): Boolean {
                return !fabButton.isOpen
            }

            override fun isHalfHoveringExpend(): Boolean {
                return fabButton.isHalfHoveringExpend
            }

            override fun onHalfHoveringStateChangeStart(expand: Boolean) {
                Timber.d("onHalfHoveringStateChangeStart...")
                fabButton.halfHovering(expand)
            }

            override fun onHalfHoveringStateChangeEnd(expand: Boolean) {
                Timber.d("onHalfHoveringStateChangeEnd...")
            }
        })

        // Drawer stuff
        navDrawerList.setHasFixedSize(true)
        navDrawerList.layoutManager = androidx.recyclerview.widget.LinearLayoutManager(this)

        navAdapter = FeedsAdapter(object : AbstractOnNavigationItemClickListener() {
            override fun onNavigationItemClick(id: Long, displayTitle: String?, url: String?, tag: String?) {
                drawerLayout.closeDrawer(GravityCompat.START)
                //if (navController.currentDestination?.id == R.id.feedFragment) {
                navController.navigate(R.id.action_feedFragment_pop, bundle {
                    putLong(ARG.FEED_ID, id)
                    putString(ARG.TITLE, displayTitle)
                    putString(ARG.LINK, url)
                    putString(ARG.TAG, tag)
                })
                //}
            }

            override fun deleteFeed(id: Long) {
                if (navController.currentDestination?.id == R.id.feedFragment&& PrefUtils.getLastOpenFeedId(this@FeedActivity)==id) {
                    navController.navigate(R.id.action_feedFragment_pop, bundle {
                        putLong(ARG.FEED_ID, ID_ALL_FEEDS)
                    })
                }
                super.deleteFeed(id)
            }

            override fun deleteFeedsInTag(tag: String) {
                super.deleteFeedsInTag(tag)
                navController.navigate(R.id.action_feedFragment_pop, bundle {
                    putLong(ARG.FEED_ID, ID_ALL_FEEDS)
                })
            }

            override fun showFeedRule(feedId: Long) {
                showFeedRuleActivity(feedId)
            }
        })
        navDrawerList.adapter = navAdapter

        // Navigation stuff
        navController.addOnDestinationChangedListener { _, destination, _ ->
            Timber.d("call on Navigation change listener")

            // Drawer handling
            when (destination.id) {
                R.id.feedFragment -> {
                    drawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_UNLOCKED)
                }
                else -> {
                    drawerLayout.setDrawerLockMode(DrawerLayout.LOCK_MODE_LOCKED_CLOSED)
                }
            }

            // Fab handling
            when (destination.id) {
                R.id.feedFragment,R.id.readerFragment  -> {
                    fabButton.show()
                }
                else -> {
                    fabButton.clearActionItems()
                    fabButton.hide()
                }
            }

            // Toolbar hiding
            when (destination.id) {
                //R.id.feedFragment -> fixedToolbar()
                R.id.feedFragment -> hideableToolbar()
                R.id.readerFragment -> hideableToolbar()
                R.id.codeViewFragment -> hideableToolbar()
                R.id.readerWebViewFragment -> hideableToolbar()
                else -> fixedToolbar()
            }
        }
    }


    override fun onResume() {
        super.onResume()
        lifecycleScope.launch {
            handler.postDelayed({ syncFeedsMaybe() },1000)
        }
    }


    override fun getFab(): AdvSpeedDialView = fabButton

    override fun navHostFragment(): Int =R.id.nav_host_fragment

    override fun getToolBar(): Toolbar=toolbar

    override fun handleSettingIntent() {
        if (intent?.action == Intent.ACTION_MANAGE_NETWORK_USAGE) {
            navController.navigate(R.id.settingsFragment)
        }
    }

    override fun navigateToFeedRuleFragment(feedId: Long?, regContent: String?, adFlag: Boolean?) {
        navController.navigate(R.id.action_global_feedRuleEditorDialog, bundle {
            feedId?.let { putLong(ARG.FEED_ID, feedId)}
            regContent?.let {  putString("regContext", regContent)}
            adFlag?.let {  putBoolean(ARG.AD_FLAG,adFlag) }
        })
    }


    override fun onAttachedToWindow() {
        super.onAttachedToWindow()
        val callback: OnBackPressedCallback = object : OnBackPressedCallback(
            true // default to enabled
        ) {
            override fun handleOnBackPressed() {
                backPressedCheck()
            }
        }
        onBackPressedDispatcher.addCallback(
            this,  // LifecycleOwner
            callback
        )
    }


    @OptIn(InternalCoroutinesApi::class, FlowPreview::class)
    private fun backPressedCheck() {
        if (drawerLayout.isDrawerOpen(GravityCompat.START)) {
            drawerLayout.closeDrawer(GravityCompat.START)
        } else {
             supportFragmentManager
                .primaryNavigationFragment
                ?.childFragmentManager
                ?.primaryNavigationFragment.let {
                    when (it) {
                        is ReaderWebViewFragment -> it.goBack().isFalse {  navController.navigateUp() }
                        is FeedFragment ->{
                            twiceCheckDelay.call()
                        }
                        else -> navController.navigateUp()
                    }
                }
        }
    }

    override fun openNavDrawer() {
        drawerLayout.openDrawer(GravityCompat.START)
    }

}